Мета: Розробити застосунок, який повинен вивантажувати дані з відкритих джерел про погодні умови (температуру денну, температуру нічну, напрям і швидкість вітру, вологість і т. ін.) для заданого населеного пункту (пунктів) для заданого часового інтервалу.

Хід роботи

1. Завантаження даних

Задамо параметри для міста Київ та часового інтервалу.

library(httr)    
## Warning: package 'httr' was built under R version 4.5.2
library(jsonlite) 
## Warning: package 'jsonlite' was built under R version 4.5.2
library(dplyr)     
## 
## Attaching package: 'dplyr'
## The following objects are masked from 'package:stats':
## 
##     filter, lag
## The following objects are masked from 'package:base':
## 
##     intersect, setdiff, setequal, union
library(lubridate) 
## Warning: package 'lubridate' was built under R version 4.5.2
## 
## Attaching package: 'lubridate'
## The following objects are masked from 'package:base':
## 
##     date, intersect, setdiff, union
library(plotly)
## Warning: package 'plotly' was built under R version 4.5.2
## Loading required package: ggplot2
## 
## Attaching package: 'plotly'
## The following object is masked from 'package:ggplot2':
## 
##     last_plot
## The following object is masked from 'package:httr':
## 
##     config
## The following object is masked from 'package:stats':
## 
##     filter
## The following object is masked from 'package:graphics':
## 
##     layout
library(DT)
## Warning: package 'DT' was built under R version 4.5.2
library(leaflet)
## Warning: package 'leaflet' was built under R version 4.5.2
city_name <- "Kremenchuk"
lat <- 49.0630   
lon <- 33.4040 
start_date <- "2010-01-01"
end_date <- "2018-12-31"

url <- paste0(
  "https://archive-api.open-meteo.com/v1/archive?",
  "latitude=", lat, "&longitude=", lon, 
  "&start_date=", start_date, "&end_date=", end_date,
  "&daily=temperature_2m_max,temperature_2m_min,wind_speed_10m_max,precipitation_sum",
  "&timezone=auto"
)

response <- GET(url)
data_raw <- fromJSON(content(response, as = "text"))

weather_df <- data.frame(
  date = as.Date(data_raw$daily$time),
  temp_day = data_raw$daily$temperature_2m_max,   # Денна
  temp_night = data_raw$daily$temperature_2m_min, # Нічна
  wind_max = data_raw$daily$wind_speed_10m_max,
  precip = data_raw$daily$precipitation_sum
)

weather_df <- weather_df %>%
  mutate(
    year = factor(year(date)),
    month = month(date, label = TRUE, abbr = FALSE),
    month_num = month(date)
  )

head(weather_df)

2. Обробка даних (Середньомісячні значення)

Розрахуємо середню температуру за кожен місяць для кожного року окремо.

monthly_avg <- weather_df %>%
  group_by(year, month, month_num) %>%
  summarise(
    avg_temp_day = round(mean(temp_day, na.rm = TRUE), 1),
    avg_temp_night = round(mean(temp_night, na.rm = TRUE), 1),
    avg_wind = round(mean(wind_max, na.rm = TRUE), 1),
    sum_precip = round(sum(precip, na.rm = TRUE), 1), 
    .groups = "drop"
  ) %>%
  arrange(year, month_num)

3. Інтерактивний графік (Plotly)

Будуємо криві динаміки температури. Вісь X — місяці, кожна лінія — окремий рік.

plot_ly(data = monthly_avg, 
        x = ~month, 
        y = ~avg_temp_day, 
        color = ~year, 
        colors = "Paired",
        type = 'scatter', 
        mode = 'lines+markers',
        text = ~paste("Рік:", year, 
                      "<br>Т.день:", avg_temp_day, "°C",
                      "<br>Т.ніч:", avg_temp_night, "°C",
                      "<br>Вітер:", avg_wind, "м/с"),
        hoverinfo = "text") %>%
  layout(
    title = paste("Динаміка середньомісячної денної температури у м.", city_name),
    xaxis = list(title = "Місяць"),
    yaxis = list(title = "Температура (°C)"),
    hovermode = "x unified"
  )

4. Інтерактивна таблиця (DT)

Таблиця з даними, яку можна сортувати та фільтрувати.

datatable(monthly_avg, 
          options = list(pageLength = 12, scrollX = TRUE),
          filter = 'top',
          colnames = c("Рік", "Місяць", "№ Місяця", "Т.День", "Т.Ніч", "Вітер", "Опади"),
          caption = "Таблиця середньомісячних показників")

5. Картограма (Leaflet)

Відображення пункту на карті.

if (!exists("lat") || !exists("lon")) {
  stop("Координати не задані! Запустіть перший блок коду (get_data).")
}

my_map <- leaflet() %>%
  addTiles() %>%
  addMarkers(lng = lon, lat = lat, popup = paste("Населений пункт:", city_name)) %>%
  setView(lng = lon, lat = lat, zoom = 10)

my_map